/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.yatb.trac.controller;

import com.yatb.trac.controller.validator.ManageTicketValidator;
import com.yatb.trac.pojo.Allegati;
import com.yatb.trac.pojo.Evento;
import com.yatb.trac.pojo.Progetti;
import com.yatb.trac.pojo.StoricoTicket;
import com.yatb.trac.pojo.Tickets;
import com.yatb.trac.pojo.condition.AllegatiFinderBySessioneUtenteWeb;
import com.yatb.trac.pojo.wrappers.StatiView;
import com.yatb.trac.pojo.wrappers.TicketView;
import com.yatb.trac.pojo.wrappers.UtentiView;
import com.yatb.trac.service.MailSenderService;
import com.yatb.trac.service.ManageTicketService;
import com.yatb.trac.service.SearchService;
import com.yatb.trac.util.SQLCondition;
import com.yatb.trac.util.StatoConstant;
import com.yatb.trac.web.form.TicketForm;

import java.math.BigDecimal;
import java.util.Arrays;
import java.util.Comparator;
import java.util.Date;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.collections.SetUtils;
import org.hibernate.criterion.Criterion;
import org.hibernate.criterion.Restrictions;
import org.springframework.util.CollectionUtils;
import org.springframework.validation.BindException;
import org.springframework.validation.ValidationUtils;
import org.springframework.validation.Validator;
import org.springframework.web.bind.ServletRequestDataBinder;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.commons.CommonsMultipartFile;
import org.springframework.web.multipart.support.ByteArrayMultipartFileEditor;
import org.springframework.web.multipart.support.DefaultMultipartHttpServletRequest;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.mvc.SimpleFormController;
import org.springframework.web.servlet.support.RequestContextUtils;

/**
 * 
 * @author edoardo
 */
public class ManageTicketController extends SimpleFormController {

	private ManageTicketService manageTicketService;
	private SearchService searchService;
	private MailSenderService mailSenderService;
	private String onCloseTicketView;

	public MailSenderService getMailSenderService() {
		return mailSenderService;
	}

	public void setMailSenderService(MailSenderService mailSenderService) {
		this.mailSenderService = mailSenderService;
	}

	public ManageTicketController() {
		// Initialize controller properties here or
		// in the Web Application Context
		// setCommandClass(MyCommand.class);
		// setCommandName("MyCommandName");
		// setSuccessView("successView");
		// setFormView("formView");
	}

	@Override
	protected ModelAndView onSubmit(HttpServletRequest request,
			HttpServletResponse response, Object command, BindException errors)
			throws Exception {
		ModelAndView mv = null;
		if (request.getParameter("inserisci") != null) {
			TicketForm tf = (TicketForm) command;
			String idTicket = tf.getIdTicket();
			Date modifyDate = new Date();
			StoricoTicket st = new StoricoTicket();
			UtentiView utenteLoggato = ControllerUtils
					.getUtenteLoggato(request);
			byte[] contents = tf.getFile();
			Tickets t = new Tickets();
			if (idTicket == null || "".equals(idTicket)) {
				// inserimento nuovo ticket
//				t.setIdProgetto(new BigDecimal(tf.getIdProgetto()));
				t.setIdProgetto(new BigDecimal(request.getParameter("idProgetto")));
				t.setStati(StatoConstant.APERTO);
				t.setDataInserimento(modifyDate);
				t.setDataUltimaModifica(modifyDate);
				st.setDescrizione(tf.getDescrizione());
				st.setDataModifica(modifyDate);
				// t.setUtentiByIdOwner(((UtentiView)
				// request.getSession().getAttribute("loginForm")).getUtenti());
				t.setUtentiByIdUtenteUltimaModifica(((UtentiView) request
						.getSession().getAttribute("loginForm")).getUtenti());
				t.setUtentiByIdUtente(((UtentiView) request.getSession()
						.getAttribute("loginForm")).getUtenti());
				st.setUtenti(((UtentiView) request.getSession().getAttribute(
						"loginForm")).getUtenti());
				st.setTickets(t);
				t.setTitoloTicket(tf.getTitoloTicket());
				TicketView tv = new TicketView();
				tv.setTickets(t);

				tv = manageTicketService.insertNewTicket(tv);
				manageTicketService.insertStoricoTck(st);
			} else {
				TicketView[] ticketViews = findTicketById(idTicket);
				t = ticketViews[0].getTickets();
				st.setDataModifica(modifyDate);
				st.setDescrizione(request.getParameter("descrizione"));

				if (utenteLoggato.getUtenti().getProfilo().getDescrizione()
						.equalsIgnoreCase("DEVELOPER")) {
					// st.setFatturare(Boolean.valueOf(tf.isDaFatturare()));
					String idOwner = request.getParameter("idOwner");
//					String idUtenteAssegnatario = request
//							.getParameter("idUtenteAssegnatario");
//					tf.setIdUtenteAssegnato(idUtenteAssegnatario);
					idOwner = (tf.getIdUtenteAssegnato() != null || !"-1"
							.equals(tf.getIdUtenteAssegnato())) ? tf
							.getIdUtenteAssegnato() : idOwner;
					if (null != idOwner && !"".equals(idOwner)) {
						if (tf.getIdUtenteAssegnato() != null
								&& !tf.getIdUtenteAssegnato().equals("-1")) {
							t.setUtentiByIdOwner(getSearchService()
									.findUtenteById(idOwner));
						}
					}
					if (tf.getGiorniConsuntivati() != null
							&& !"".equals(tf.getGiorniConsuntivati())) {
						st.setGiorniConsuntivo(tf.getGiorniConsuntivati());
					}
					if (tf.getGiorniPrevisti() != null
							&& !"".equals(tf.getGiorniPrevisti())) {
						st.setGiorniPrevisti(tf.getGiorniPrevisti());
					}
					if (tf.getOreConsuntivate() != null
							&& !"".equals(tf.getOreConsuntivate())) {
						st.setOreConsuntivo(tf.getOreConsuntivate());
					}
					if (tf.getOrePreviste() != null
							&& !"".equals(tf.getOrePreviste())) {
						st.setOrePreviste(tf.getOrePreviste());
					}
					st.setProssimaAzione(tf.getProssimaAzione());
					st.setUtenti(utenteLoggato.getUtenti());
					StatiView sv = new StatiView();
					sv.getStati().setIdStato(
							new BigDecimal(request.getParameter("idStato")));
					t.setStati(sv.getStati());
				}
				t.setDataUltimaModifica(modifyDate);
				t.setUtentiByIdUtenteUltimaModifica(utenteLoggato.getUtenti());
				st.setTickets(t);
				st.setUtenti(((UtentiView) request.getSession().getAttribute(
						"loginForm")).getUtenti());
				st = manageTicketService.updateTicket(ticketViews[0], st);
				// inserimento di un nuovo record su storico tickets e update su
				// tickets

			}
			Allegati[] allegati = findAllegati(new AllegatiFinderBySessioneUtenteWeb(
					request.getSession().getId()));
			for (int i = 0; i < allegati.length; i++) {
				Allegati a = allegati[i];
				a.setStoricoTicket(st);
				a.setTickets(t);
				a.setTemporaneo(false);
				a.setSessioneUtente(null);

				manageTicketService.updateAllegato(a);
			}

			Evento evento = new Evento();
			evento.setDataCreazione(modifyDate);
			evento.setInviato("0");
			evento.setStoricoTicket(st);
			evento.setTipoEvento("INFO");
			manageTicketService.insertEventoDaInviare(evento);

			// UtentiView[] u =
			// searchService.findUtentiAbilitatiProgettoByProfilo(new
			// UtentiView());
			if ((request.getParameter("idStato") != null && !"".equals(request
					.getParameter("idStato")))
					&& new BigDecimal(request.getParameter("idStato"))
							.intValue() == StatoConstant.CHIUSO.getIdStato()
							.intValue()) {
				request.setAttribute("idTicket", t.getIdTicket());
				mv = new ModelAndView(getOnCloseTicketView() + "?idTicket="
						+ t.getIdTicket());
				request.getSession(false).setAttribute("ticketClosed", t);
				request.getSession(false).setAttribute("storicoFatturato", st);
			} else {
				mv = new ModelAndView(getSuccessView());
				request.getSession().setAttribute("nextPage", "/search.do");
			}
		}
		return mv;
	}

	public String getOnCloseTicketView() {
		return onCloseTicketView;
	}

	@Override
	protected ModelAndView showForm(HttpServletRequest request,
			HttpServletResponse response, BindException errors)
			throws Exception {
		Map model = new HashMap();
		TicketForm tf = new TicketForm();
		boolean insert = true;
		final String idTicket = request.getParameter("idTicket");
		if (idTicket != null && !"".equals(idTicket)) {
			tf.setIdTicket(idTicket);
			insert = false;
		}
		UtentiView utenteLoggato = (UtentiView) request.getSession()
				.getAttribute("loginForm");

		tf.setIdUtente(utenteLoggato.getUtenti().getIdUtente().toPlainString());
		// qui andra' messo l'owner del ticket
		if (insert) {
			if (utenteLoggato.getUtenti().getProfilo().getDescrizione()
					.equalsIgnoreCase("DEVELOPER")) {
				ModelAndView mv = new ModelAndView(getSuccessView());
				request.getSession().setAttribute("nextPage", "/search.do");
				return mv;
			}
			Progetti[] progettis = (Progetti[]) utenteLoggato.getUtenti()
					.getProgettis().toArray(new Progetti[0]);
			tf.setListaProgetti(progettis);
			if(progettis.length==1){
				tf.setIdProgetto(progettis[0].getIdProgetto().toPlainString());
				tf.setDescrizioneProgetto(progettis[0].getDescrizione());
				
			}
//			tf.setIdProgetto(progettis[0].getIdProgetto().toPlainString());
//			tf.setDescrizioneProgetto(progettis[0].getDescrizione());
		} else {
			Tickets tickets = findTicketById(idTicket)[0].getTickets();
			if (tickets.getUtentiByIdOwner() != null) {
				tf.setIdOwner(tickets.getUtentiByIdOwner().getIdUtente()
						.toPlainString());
			}

			Progetti[] progetti = new Progetti[]{getSearchService().findProgettoByTicket(
					tf.getIdTicket())};
			if (progetti != null) {
				tf.setListaProgetti(progetti);
				tf.setIdProgetto(progetti[0].getIdProgetto().toPlainString());
				tf.setDescrizioneProgetto(progetti[0].getDescrizione());
			}
			if (utenteLoggato.getUtenti().getProfilo().getDescrizione().equals(
					"DEVELOPER")) {

				// UtentiView[] utentiViews = searchService
				// .findUtentiAbilitatiProgettoByProfilo(tickets
				// .getIdProgetto().toPlainString(), utenteLoggato
				// .getUtenti().getProfilo());
				// request.setAttribute("assegnatari", CollectionUtils
				// .arrayToList(utentiViews));
				if (tickets.getUtentiByIdOwner() != null) {
					request.setAttribute("owner", tickets.getUtentiByIdOwner());
				}
				// StatiView[] stati = searchService.findAllStati();
				// model.put("stati", stati);

			}
			StoricoTicket[] storico = (StoricoTicket[]) tickets
					.getStoricoTickets().toArray(new StoricoTicket[0]);
			Arrays.sort(storico, new Comparator<StoricoTicket>() {

				public int compare(StoricoTicket o1, StoricoTicket o2) {
					return o1.getIdStorico().compareTo(o2.getIdStorico()) * -1;
				}
			});
			tf.setDescrizione(storico[0].getDescrizione());
			tf.setTitoloTicket(tickets.getTitoloTicket());
//			tf.setIdOwner(tickets.getUtentiByIdOwner().getIdUtente());
			request.setAttribute("idStato", tickets.getStati().getIdStato());
		}
		model.put("ticket", tf);
		model.put("action", "inserisciTicket.do");
		return showForm(request, errors, getFormView(), model);
	}

	@Override
	protected void initBinder(HttpServletRequest request,
			ServletRequestDataBinder binder) throws Exception {
		binder.registerCustomEditor(byte[].class,
				new ByteArrayMultipartFileEditor());
	}

	private TicketView[] findTicketById(final String idTicket) {
		TicketView[] tickets = getSearchService().findTickets(
				new SQLCondition() {

					public Criterion create(Object... params) {
						return Restrictions.eq("idTicket", new BigDecimal(
								idTicket));
					}
				});
		return tickets;
	}

	public ManageTicketService getManageTicketService() {
		return manageTicketService;
	}

	public void setManageTicketService(ManageTicketService manageTicketService) {
		this.manageTicketService = manageTicketService;
	}

	public SearchService getSearchService() {
		return searchService;
	}

	public void setSearchService(SearchService searchService) {
		this.searchService = searchService;
	}

	public Allegati[] findAllegati(SQLCondition sqlCondition) {
		return getSearchService().find(new Allegati[0], sqlCondition,
				Allegati.class);
	}

	@Override
	public ModelAndView handleRequest(HttpServletRequest request,
			HttpServletResponse response) throws Exception {
		SQLCondition sqlCondition = new AllegatiFinderBySessioneUtenteWeb(
				request.getSession().getId());
		Allegati[] listaAllegatiTemporanei = findAllegati(sqlCondition);

		request.setAttribute("allegati", listaAllegatiTemporanei);

		return super.handleRequest(request, response);
	}

	public void setOnCloseTicketView(String onCloseTicketView) {
		this.onCloseTicketView = onCloseTicketView;
	}

	@Override
	protected void onBindAndValidate(HttpServletRequest request,
			Object command, BindException errors) throws Exception {
		ManageTicketValidator validator = (ManageTicketValidator) getValidator();
		validator.validateRequestParams(request, errors, command);
	}

}
